import java.awt.Component;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.Vector;

import javax.swing.AbstractCellEditor;
import javax.swing.DefaultCellEditor;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JComboBox;
import javax.swing.JProgressBar;
import javax.swing.JTable;
import javax.swing.SwingConstants;
import javax.swing.table.AbstractTableModel;
import javax.swing.table.DefaultTableCellRenderer;
import javax.swing.table.TableCellEditor;
import javax.swing.table.TableCellRenderer;
import javax.swing.table.TableColumn;
import javax.swing.table.TableColumnModel;


@SuppressWarnings("serial")
public class FolderTable extends JTable {
	private final String TableHeaderName[] = { "Folder", "Progress", "Size", "Size", 
			"Quality", "Scale", "IPad", "Del", "View Src", "View Dst" };
	static final int FOLDER_COL = 0;
	static final int PROGRESS_COL = 1;
	static final int ORGSIZE_COL = 2;
	static final int SIZE_COL = 3;
	static final int QUALITY_COL = 4;
	static final int SCALE_COL = 5;
	static final int IPAD_COL = 6;
	static final int DEL_COL = 7;
	static final int VIEWO_COL = 8;
	static final int VIEWD_COL = 9;

	JButton butnDel;
	JButton butnViewSrc;
	JButton butnViewDst;
	JCheckBox chkIPad;
	JProgressBar progressWork;

	private Vector<FolderData> oTableData;

	public FolderTable() {
		
		this.setRowHeight(20);
		this.setModel(new FolderTableModel());

		oTableData = new Vector<FolderData>();

		butnDel = new JButton("DEL");
		butnViewSrc = new JButton("Src");
		butnViewDst = new JButton("Dst");
		chkIPad = new JCheckBox();
		progressWork = new JProgressBar();

		TableColumnModel mdlCol = this.getColumnModel();

		mdlCol.getColumn(FOLDER_COL).setPreferredWidth(500);

		mdlCol.getColumn(PROGRESS_COL).setCellRenderer(new ProgressRenderer());
		mdlCol.getColumn(PROGRESS_COL).setPreferredWidth(150);

		DefaultTableCellRenderer dtcr = new DefaultTableCellRenderer();
		dtcr.setHorizontalAlignment(SwingConstants.RIGHT);
		mdlCol.getColumn(ORGSIZE_COL).setCellRenderer(dtcr);
		mdlCol.getColumn(SIZE_COL).setCellRenderer(dtcr);

		setupQualityColumn(mdlCol.getColumn(QUALITY_COL));
		setupScaleColumn(mdlCol.getColumn(SCALE_COL));
		
		mdlCol.getColumn(DEL_COL).setCellRenderer(new ButtonRenderer());
		mdlCol.getColumn(DEL_COL).setCellEditor(new ButtonEditor());
		
		mdlCol.getColumn(VIEWO_COL).setCellRenderer(new ButtonRenderer());
		mdlCol.getColumn(VIEWO_COL).setCellEditor(new ButtonEditor());

		mdlCol.getColumn(VIEWD_COL).setCellRenderer(new ButtonRenderer());
		mdlCol.getColumn(VIEWD_COL).setCellEditor(new ButtonEditor());
	}

	public void AddData(String folderName, long Size, long SizeDst) {
		oTableData.add(new FolderData(folderName, (int)(Size/(1024*1024)), (int)(SizeDst/(1024*1024)), 85, 100, false));
	}
	
	public void SetDstSize(long SizeDst, int row) {
		int size = (int)(SizeDst/(1024*1024));
		getModel().setValueAt(Integer.toString(size)+" MB", row, SIZE_COL);
	}

	public void RemoveData(int index) {
		oTableData.remove(index);
		((AbstractTableModel)this.getModel()).fireTableDataChanged();
		requestFocusInWindow();
	}

	public String GetData(int row, int column) {
		Object oData = oTableData.get(row).GetObject(column);
		if (oData == null) return null;
		else return oData.toString();
	}

	private void setupScaleColumn(TableColumn scaleColumn) {
		//Set up the editor for the sport cells.
		String[] comboItem = {"50%", "75%", "100%"};
		JComboBox comboBox = new JComboBox(comboItem);
		scaleColumn.setCellEditor(new DefaultCellEditor(comboBox));
		scaleColumn.setPreferredWidth(60);
	}

	private void setupQualityColumn(TableColumn qualityColumn) {
		//Set up the editor for the sport cells.
		String[] comboItem = { "70", "75", "80", "85", "90", "95", "100"};
		JComboBox comboBox = new JComboBox(comboItem);
		qualityColumn.setCellEditor(new DefaultCellEditor(comboBox));
		qualityColumn.setPreferredWidth(60);
	}	 


	private class ButtonRenderer implements TableCellRenderer {

		@Override
		public Component getTableCellRendererComponent(JTable table,
				Object value, boolean isSelected, boolean hasFocus, int row, int column) {

			if (column == DEL_COL) return butnDel;
			else if (column == VIEWO_COL) return butnViewSrc;
			else if (column == VIEWD_COL) return butnViewDst;
			else return null;
		}
	}
	
	private class ProgressRenderer implements TableCellRenderer {

		@Override
		public Component getTableCellRendererComponent(JTable table,
				Object value, boolean isSelected, boolean hasFocus, int row, int column) {

			int Progress = (Integer)oTableData.get(row).GetObject(column);
			progressWork.setValue(Progress);
			return progressWork;
		}
	}
	
	private class ButtonEditor extends AbstractCellEditor implements TableCellEditor, ActionListener {

		private JButton editComp = null;

		public ButtonEditor() {
			super();
			editComp = new JButton();
			editComp.addActionListener(this);
		}

		@Override
		public Object getCellEditorValue() { return butnDel.getText(); }

		@Override
		public void actionPerformed(ActionEvent e) {
			fireEditingStopped();
		}

		@Override
		public Component getTableCellEditorComponent(JTable table, Object value,
				boolean isSelected, int row, int column) {
			if (column == DEL_COL) editComp.setText("DEL");
			else if (column == VIEWO_COL) editComp.setText("Src");
			else if (column == VIEWD_COL) editComp.setText("Dst");

			return editComp;
		}
		
	}

	private class FolderTableModel extends AbstractTableModel {

		@Override
		public int getColumnCount() { return TableHeaderName.length; }

		@Override
		public String getColumnName(int column) { return TableHeaderName[column];}

		@Override
		public int getRowCount() { return oTableData.size(); }

		@Override
		public Object getValueAt(int row, int column) { return oTableData.get(row).GetObject(column); }

		@Override
		public void setValueAt(Object value, int row, int column) {
			oTableData.get(row).SetObject(column, value);
			fireTableCellUpdated(row, column);
		}

		public Class<?> getColumnClass(int column) { return oTableData.get(0).GetObject(column).getClass(); }

		@Override
		public boolean isCellEditable(int row, int column) {
			switch (column) {
			case QUALITY_COL:
			case SCALE_COL:
			case IPAD_COL:
			case DEL_COL:
			case VIEWO_COL:
			case VIEWD_COL:
				return true;
			default:
				return false;
			}
		}

	}

	private class FolderData {

		private final int DataSize = 7;

		Object oData[];

		public FolderData(String folderName, int Size, int SizeDst, int Quality, int Scale, boolean Pad) {
			super();
			
			oData = new Object[DataSize];
			oData[0] = folderName;
			oData[1] = 0;
			oData[2] = Integer.toString(Size)+" MB";
			oData[3] = Integer.toString(SizeDst)+" MB";
			oData[4] = Integer.toString(Quality);
			oData[5] = Integer.toString(Scale)+"%";
			oData[6] = Pad;
		}

		public Object GetObject(int idx) {
			if (idx < DataSize) return oData[idx];
			else return null;
		}

		public void SetObject(int idx, Object value) {
			if (idx < DataSize) oData[idx] = value;
		}

	}
}
